const qiniu =require('qiniu')
const fs = require('fs');
const accessKey = '-CSpqYXf6r4hMWrN7vKYrGgQlP_jUNp5eF8uMRDs'
const secretKey = 'y95iOAv-kQdhf0nw5BoLM2Nnyd8pZY4H_bBhZgXi'
var mac = new qiniu.auth.digest.Mac(accessKey, secretKey)
const bucket = 'yoogor'
const config = new qiniu.conf.Config()
const bucketManager = new qiniu.rs.BucketManager(mac, config)
var domain = '';
/**
 * 获取上传token
 */
const uploadToken = () => {
  var options = {
    scope: bucket
  }
  var putPolicy = new qiniu.rs.PutPolicy(options)
  return putPolicy.uploadToken(mac)
}

/**
 * 获取上传token
 * @param {*} overideKey overideKey
 */
const overrideUploadToken = overideKey => {
  var options = {
    scope: bucket + ':' + overideKey
  }
  var putPolicy = new qiniu.rs.PutPolicy(options)
  return putPolicy.uploadToken(mac)
}

/**
 * 文件上传
 * @param {*} filePath filePath
 * @param {*} key key
 * @param {*} uploadToken uploadToken
 * @param {*} callback callback
 */
const uploadFile = (filePath, key, uploadToken, callback) => {
  var formUploader = new qiniu.form_up.FormUploader(config)
  var putExtra = new qiniu.form_up.PutExtra()
  formUploader.putFile(
    uploadToken,
    key,
    filePath,
    putExtra,
    (respErr, respBody, respInfo) => {
      if (respErr) {
        callback(respErr)
      }
      if (respInfo.statusCode === 200) {
        callback(null, respBody)
      } else {
        console.log(respInfo.statusCode)
        callback(null, respBody)
      }
    }
  )
}

/**
 * 文件上传
 * @param {*} filePath filePath
 * @param {*} key key
 * @param {*} uploadToken uploadToken
 * @param {*} callback callback
 */
const uploadFileNew = (filePath, key, uploadToken) => {
  var formUploader = new qiniu.form_up.FormUploader(config)
  var putExtra = new qiniu.form_up.PutExtra()
  return new Promise((reslove,reject)=>{
    formUploader.putFile(
      uploadToken,
      key,
      filePath,
      putExtra,
      (respErr, respBody, respInfo) => {
        if (respErr) {
          reject(respErr)
        }
        if (respInfo.statusCode === 200) {
          reslove(respBody)
        } else {
          console.log(respInfo.statusCode)
          reslove(respBody)
        }
      }
    )
  })
  
}

/**
 * 文件信息查询
 * @param {*} key 文件
 * @param {*} callback callback
 */
const fileState = (key, callback) => {
  bucketManager.stat(bucket, key, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      if (respInfo.statusCode === 200) {
        callback(null, respBody)
      } else {
        console.log(err)
      }
    }
  })
}

/**
 * 文件移动
 * @param {*} param0 param0
 * @param {*} callback callback
 */
const fileMove = ({srcKey, destKey}, callback) => {
  var options = {
    force: true
  }
  bucketManager.move(bucket, srcKey, bucket, destKey, options, (
    err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      console.log(respInfo.statusCode)
      callback(null, respBody)
    }
  })
}

/**
 * 文件复制
 * @param {*} param0 param0
 * @param {*} callback callback
 */
const fileCopy = ({srcKey, destKey}, callback) => {
  var options = {
    force: true
  }
  bucketManager.copy(bucket, srcKey, bucket, destKey, options, (
    err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      console.log(respInfo.statusCode)
      callback(null, respBody)
    }
  })
}

/**
 * 文件删除
 * @param {*} key 文件
 * @param {*} callback callback
 */
const fileDel = (key, callback) => {
  bucketManager.delete(bucket, key, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      console.log(respInfo.statusCode)
      callback(null, respBody)
    }
  })
}

/**
 * 设置文件生命时间
 * @param {*} param0 param0
 * @param {*} callback callback
 */
const fileDelAfterDays = ({key, days}, callback) => {
  bucketManager.deleteAfterDays(bucket, key, days, (err, respBody,
    respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      console.log(respInfo.statusCode)
      callback(null, respBody)
    }
  })
}

/**
 * 查询指定前缀的文件列表
 * @param {*} param0 param0
 * @param {*} callback callback
 */
const fileList = ({pageSize, pageNum, prefix}, callback) => {
  var options = {
    limit: pageSize || 10,
    prefix: prefix || '',
    marker: pageSize * pageNum || 0
  }
  bucketManager.listPrefix(bucket, options, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    }
    if (respInfo.statusCode === 200) {
      var nextMarker = respBody.marker
      var commonPrefixes = respBody.commonPrefixes
      console.log(nextMarker)
      console.log(commonPrefixes)
      callback(null, respBody)
    } else {
      console.log(respInfo.statusCode)
      console.log(respBody)
      callback(null, respBody)
    }
  })
}

/**
 * 批量查询文件状态
 * @param {*} keys 文件
 * @param {*} callback callback
 */
const fileStateBatch = (keys, callback) => {
  var statOperations = []
  keys.forEach(element => {
    statOperations.push(qiniu.rs.statOp(bucket, element))
  })
  bucketManager.batch(statOperations, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      // 200 is success, 298 is part success
      if (parseInt(respInfo.statusCode / 100) === 2) {
        callback(null, respBody)
      } else {
        console.log(respInfo.statusCode)
        console.log(respBody)
        callback(null, respBody)
      }
    }
  })
}

/**
 * 批量删除文件
 * @param {*} keys 文件
 * @param {*} callback callback
 */
const fileDelBatch = (keys, callback) => {
  var deleteOperations = []
  keys.forEach(element => {
    deleteOperations.push(qiniu.rs.deleteOp(bucket, element))
  })
  bucketManager.batch(deleteOperations, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      // 200 is success, 298 is part success
      if (parseInt(respInfo.statusCode / 100) === 2) {
        callback(null, respBody)
      } else {
        console.log(respInfo.deleteusCode)
        console.log(respBody)
        callback(null, respBody)
      }
    }
  })
}

/**
 * 文件批量复制
 * @param {*} files 文件
 * @param {*} callback 回调
 */
const fileCopyBatch = (files, callback) => {
  var copyOperations = []
  files.forEach(element => {
    copyOperations.push(qiniu.rs.copyOp(bucket, element.srcKey, bucket, element.destKey))
  })
  bucketManager.batch(copyOperations, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      // 200 is success, 298 is part success
      if (parseInt(respInfo.statusCode / 100) === 2) {
        callback(null, respBody)
      } else {
        console.log(respInfo.deleteusCode)
        console.log(respBody)
        callback(null, respBody)
      }
    }
  })
}

/**
 * 文件批量移动
 * @param {*} files 文件
 * @param {*} callback 回调
 */
const fileMoveBatch = (files, callback) => {
  var moveOperations = []
  files.forEach(element => {
    moveOperations.push(qiniu.rs.moveOp(bucket, element.srcKey, bucket, element.destKey))
  })
  bucketManager.batch(moveOperations, (err, respBody, respInfo) => {
    if (err) {
      console.log(err)
      callback(err, null)
    } else {
      // 200 is success, 298 is part success
      if (parseInt(respInfo.statusCode / 100) === 2) {
        callback(null, respBody)
      } else {
        console.log(respInfo.deleteusCode)
        console.log(respBody)
        callback(null, respBody)
      }
    }
  })
}

var http = require('http');
var request = require('request');

const getFileDomain = () => {
  return new Promise((reslove,reject)=>{
    if(domain) {
      reslove(domain);
    }else {
      const accessToken = qiniu.util.generateAccessToken(mac,'http://api.qiniu.com/v6/domain/list?tbl='+bucket,'');
      var options = {  
        hostname: 'api.qiniu.com',  
        path: '/v6/domain/list?tbl=' + bucket,  
        method: 'GET'  ,
        headers: {
          Authorization: accessToken,
          'Content-Type':'application/x-www-form-urlencoded'
        }
      };  
      var req = http.request(options, (res) => {  
        console.log('STATUS: ' + res.statusCode);  
        console.log('HEADERS: ' + JSON.stringify(res.headers));  
        res.setEncoding('utf8');  
        let body = '';
        res.on('data', (chunk) => {  
          body +=chunk
        });  
        res.on('end',()=>{
          const body1 = JSON.parse(body);
          if(body1.length>0) {
            domain = body1[0];
            reslove(domain);
          }else {
            reslove('');
          }
        });
      });  
      req.on('error', (e) => {  
        console.log('problem with request: ' + e.message);  
      });  
      req.end()
    }
  })
}

const downloadFile = (url,dest) => {
  console.log(url,dest)
  return new Promise((reslove,reject) => {
    var writable = fs.createWriteStream(dest,{
      flags: 'w',
      mode: 0666,
    });
    writable.on('finish', function(){
      reslove()
    });
    writable.on('error', function(err){
      reject(err)
    });
    request(url).pipe(writable);
  })
}

module.exports = {
  uploadFileNew,
  overrideUploadToken,
  uploadToken,
  fileCopy,
  fileCopyBatch,
  fileDel,
  fileDelBatch,
  fileDelAfterDays,
  fileList,
  fileMove,
  fileMoveBatch,
  fileState,
  fileStateBatch,
  getFileDomain,
  downloadFile
}
